<!--场景的目录树 虚拟滚动树-->
<template>
  <lay-card>
    <lay-layer
        title="编辑名称"
        v-model="visibleTable"
        :shade="false"
        :area="['500px', '260px']"
        :offset="['10%', '30%']"
    >
      <div style="padding: 20px;">
        <AddSceneType
            :operate="currentNodeFlag"
            :currentNode="currentNode"
            @updateNode="updateNodeAndPushRoute"
        ></AddSceneType>
      </div>
    </lay-layer>
    <lay-row space="10">
      <lay-col>
        <lay-input
          v-model="queryName"
          :allow-clear="true"
          @clear="clearAndGetLinks"
          size="sm"
          placeholder="请输入查询，区分大小写"
          @change="filterDbTrees"
          >
            <template #suffix>
              <lay-icon type="layui-icon-search" @click="filterDbTrees" size="sm"></lay-icon>
            </template>
          </lay-input>
      </lay-col>
    </lay-row>
    <lay-row space="10">
      <lay-col>
        <lay-button size="xs" @click="expandAllEvent">展开所有</lay-button>
        <lay-button size="xs" @click="closeExpandEvent">收起所有</lay-button>
        <lay-button size="xs" @click="submitChecked" v-if="showCheckbox === true">选定</lay-button>
        <lay-button size="xs" @click="cancelChecked" v-if="showCheckbox === true">取消</lay-button>
      </lay-col>
    </lay-row>
    <lay-row space="10">
      <lay-col>
          <vxe-table
            show-overflow
            :height="scrollHeight"
            ref="tableRef"
            border="outer"
            :round="true"
            :loading="loading"
            :show-header="false"
            :tree-config="treeConfig"
            :row-config="{isCurrent: true, height: 35, isHover: true, keyField: 'id'}"
            :checkbox-config="checkBoxConfig"
            :scroll-y="{enabled: true, gt: 20}"
            :data="tableData"
          >
            <vxe-column
              field="name"
              title="名称"
              sortable
              :type="showCheckbox === true ? 'checkbox':'seq'"
              tree-node
              isCurrent
              width="90%"
            >
              <template #default="{ row }">
                <vxe-button
                    type="text"
                    :icon="setIconButton(row)"
                    @click="handleClick(row)"
                    :class="(row.type === 'scene_id' || row.type === 'scene_group') ? 'CheckRow' : 'NoCheckRow'"
                >{{ row.name }}</vxe-button>
              </template>
            </vxe-column>
            <vxe-column title="操作" width="10%" v-if="showCheckbox !== true">
              <template #default="{ row }">
                <div>
                  <lay-icon
                    type="layui-icon-addition"
                    v-if="row.type === 'scene_root'"
                    @click="editNode('add', row)"
                    style="margin-right: 10px"
                  ></lay-icon>
                  <lay-dropdown trigger="hover" updateAtScroll>
                    <lay-icon
                      v-if="row.type !== 'scene_root'"
                      type="layui-icon-more"
                      style="margin-right: 5px"
                    ></lay-icon>
                    <template #content>
                      <lay-card>
                        <lay-row space="10" v-if="row.type === 'scene_id'">
                          <lay-col md="22">
                            <lay-dropdown-menu-item @click="viewRecord(row)">
                              <lay-icon type="layui-icon-log"></lay-icon>查看记录
                            </lay-dropdown-menu-item></lay-col>
                        </lay-row>
                        <lay-row space="10" v-if="row.type === 'scene_dir'">
                          <lay-col md="22">
                            <lay-dropdown-menu-item @click="editNode('add', row)">
                              <lay-icon type="layui-icon-add-one"></lay-icon>新增
                            </lay-dropdown-menu-item></lay-col>
                        </lay-row>
                        <lay-row space="10" v-if="row.type === 'scene_dir'">
                          <lay-col md="22">
                            <lay-dropdown-menu-item @click="editNode('copy', row)">
                              <lay-icon type="layui-icon-add-circle"></lay-icon>复制新增
                            </lay-dropdown-menu-item></lay-col>
                        </lay-row>
                        <lay-row space="10">
                          <lay-col md="22">
                            <lay-dropdown-menu-item @click="editNode('update', row)">
                              <lay-icon type="layui-icon-edit"></lay-icon>更新
                            </lay-dropdown-menu-item>
                          </lay-col>
                        </lay-row>
                        <lay-row space="10">
                          <lay-col md="22">
                            <lay-dropdown-menu-item @click="deleteNode(row)">
                              <lay-icon type="layui-icon-delete"></lay-icon>删除
                            </lay-dropdown-menu-item>
                          </lay-col>
                        </lay-row>
                      </lay-card>
                    </template>
                  </lay-dropdown>
                </div>
              </template>
            </vxe-column>
          </vxe-table>
      </lay-col>
    </lay-row>
  </lay-card>
</template>

<script lang="ts">
export default {
    name: "SceneVirtualTree"
}
</script>

<script lang="ts" setup>
import {onMounted, ref, getCurrentInstance, reactive, h} from 'vue';
import {VxeTableInstance, VxeTablePropTypes} from "vxe-table";
import {layer} from "@layui/layer-vue";
import {TreeNews} from "../../../store/databases/TreeNews";
import {RowVO} from "../../../store/interface/VirtulTreeInterface";
import router from "../../../router";
import AddSceneType from "./AddSceneType.vue";
import {deleteSceneApi, getSceneColumnApi, queryScenesApi} from "../../../api/module/scene";
import {notify} from "../../../untils/tip";

const sceneTree = new TreeNews();
const tableRef = ref<VxeTableInstance<RowVO>>();
const loading = ref(false);
const tableData = ref<RowVO[]>([]);
const tableDataTemp = ref<RowVO[]>([]); // 筛选结果表
const visibleTable = ref(false);
const currentNode = ref({});

/** 定义一个变量来接收父组件传来的方法 **/
const emit = defineEmits(["insertTables", "cancelCheck"]);

// 组件入参
const {scrollHeight, showCheckbox, checkKeys, checkedType} = defineProps({
    scrollHeight: {type: String, default: '700'},
    showCheckbox: {type: Boolean, default: false},
    checkKeys: {type: Array},
    checkedType: {type: String, default: 'scene_field'}
});

// 初始化加载方法
onMounted(() => {
  queryTreeScenes();
});

// 虚拟滚动树的配置项
const treeConfig = reactive<VxeTablePropTypes.TreeConfig<RowVO>>({
  lazy: false,       // 开启懒加载
  transform: true,  // 开启树形结构
  indent: 15,       // 树节点的缩进
  rowField: 'id',
  accordion: false,  // 对于同一级的节点，每次只能展开一个
  reserve: true,     // 是否保留展开状态
  parentField: 'parentId',
  hasChildField: 'hasChild',
  expandRowKeys: ['db_root.1'],    // 展开的节点
  // loadMethod ({ row }) {
  //   // 异步加载子节点
  //   return new Promise(resolve => {
  //     const childNodes = viewDetail(row);
  //     resolve(childNodes)
  //   })
  // }
});

// 复选框的配置项
const checkBoxConfig = reactive<VxeTablePropTypes.CheckboxConfig<RowVO>>({
  checkStrictly: true,  // 父子关联？
  checkField: 'checked',
  highlight: showCheckbox === true,
  labelField: 'name',
  checkRowKeys: checkKeys,
  reserve: true,
  checkMethod(params: { row: RowVO }): boolean {
    return params.row.type === checkedType;
  }
})

// old params
const queryName = ref('');  // 查询节点名称

// 选定
const submitChecked = () => {
  const $table = tableRef.value;
  if ($table) {
    const checkRecord = $table.getCheckboxRecords();
    console.log('submitChecked:', checkRecord, checkedType)
    if((checkedType === 'scene_id' || checkedType === 'scene_group') && checkRecord.length !== 1){
      notify('failed', '只须勾选1个！')
    }else if(checkedType === 'scene_field' && checkRecord.length === 0){
      notify('failed', '至少勾选一个！')
    }else{
      emit('insertTables', checkRecord);
    }
  }
};

// 取消
const cancelChecked = () => {
  emit('cancelCheck');
}

const updateNodeAndPushRoute = async (node:any) => {
  await queryTreeScenes();
  await handleClick(node);
}

const queryTreeScenes = async () => {
  loading.value = true
  tableData.value = [];
  let {result, status, message} = await queryScenesApi();
  if (status === 'success'){
      tableData.value = result;
      sceneTree.addNodes(result);
  }else {
      tableData.value = [
          {id: '0', hasChild: false, parentId: null, name: "场景根节点", type: "scene_root",
              checked: false, dbLink: null, dbBase: null, dbTable: null,
              dbField: null, data: null, children: []},
      ];
      notify("failed", message);
  }
  loading.value = false;
  visibleTable.value = false;
}

// 页面加载前执行的初始方法
let instance = getCurrentInstance();



// 节点树的设置和操作
const setIconButton = (row: RowVO): string => {
  const iconText = ref('vxe-icon-send');
  switch (row.type) {
    case 'scene_root' : iconText.value = 'vxe-icon-home'; break;
    case 'scene_dir' : iconText.value = 'vxe-icon-folder'; break;
    case 'scene_group': iconText.value = 'vxe-icon-square-square';break;
    case 'scene_id' : iconText.value = 'vxe-icon-feedback'; break;
  }
  return iconText.value;
};

const handleClick = async (node: any) => {
  const params = reactive({scene_id: node.id, scene_name: node.name});
  console.log('handleClick:', params, node)
  if(showCheckbox){
    if(node.type === 'scene_id' && checkedType === 'scene_field'){
      await loadSceneColumn(node);
    }
  }else {
    switch (node.type) {
    case 'scene_id' :
      router.push({name: 'EditScene', params: params});
      break;
    case 'scene_dir':
      router.push({name: 'SceneList', params: params});
      break;
    case 'scene_group':
      router.push({name: 'SceneGroup', params: params});
      break;
    default :
      router.push({name: 'NonePage'});
      break;
    }
  }

};

const loadSceneColumn = async (node: any) => {
  console.log('loadSceneColumn', node);
  if(node.type === 'scene_id' && !node.hasChild){
    // let sceneId = node.id.split('.')[1];
    const sceneIds = reactive({scene_id: node.id});
    const {result, status, message} = await getSceneColumnApi(sceneIds);
    if(status === 'success'){
      node.hasChild = true;
      result.forEach((row:RowVO) => {tableData.value.push(row);})
      const $table = tableRef.value
      $table?.loadData(tableData.value);
      $table?.toggleTreeExpand(node);
    }else {
      notify('failed', message)
    }
  }
}

// 全部展开所有节点
const expandAllEvent = () => {
  const $table = tableRef.value
  if ($table) {
    $table.setAllTreeExpand(true)
  }
};

// 全部展开所有节点
const closeExpandEvent = () => {
  const $table = tableRef.value
  if ($table) {
    $table.clearTreeExpand()
  }
};

// 清楚查询信息
const clearAndGetLinks = () => {
    tableData.value = sceneTree.getTree();
};


// 查询树，筛选树
const filterTargetTrees = (rawTreeData: any) => {
    loading.value = true;
    console.log('filterTargetTrees: ', rawTreeData )
    sceneTree.clearResultTree();
    sceneTree.filterTree(rawTreeData, (node: RowVO)=>{
        const regex_pattern = new RegExp(queryName.value, "i");
        return node.name?.match(regex_pattern);
    })
    const newTrees = sceneTree.getResultTrees();
    console.log('newTrees:', newTrees)
    if(newTrees){
       tableData.value = newTrees;
       notify("success", "查找成功，刷新页面！")
    }else {
        notify("failed", "查找失败，不存在！")
    }
    loading.value = false;
};

// 查询 逻辑如下：
const filterDbTrees = () => {
  // 0.资源清理 -- 很重要
  tableDataTemp.value = [];
  if(queryName.value.length > 0){
    const $table = tableRef.value;
    const currentData = $table?.data;
    console.log('currentData:', currentData)
    if(currentData && currentData?.length > 0){
        filterTargetTrees(currentData[0]);
    }
  }else {
    clearAndGetLinks();
  }
};

// 菜单功能
const viewRecord = (node: any) => {
  const params = reactive({scene_id: node.id});
  router.push({name: 'viewRecord', params: params});
};

const msg_id = ref();

const currentNodeFlag = ref('add');
const editNode = (oper: string, node: any) => {
  currentNodeFlag.value = oper;
  currentNode.value = node;
  visibleTable.value = true;
};

const deleteNode = (node: any) => {
  console.log('deleteNode', node)
  if(node.children.length > 0){
    layer.msg('存在不允许删除')
  }else {
    layer.confirm('确认要删除该节点么？', {
      btn: [
        {text:'确认', callback: (id: any) => {
          deleteSceneNode(node);
          layer.close(id); }
        },
        {text:'取消', callback: (id: any) => {
          layer.close(id);}
        }
      ]
    })
  }
};

const deleteSceneNode = async (node: any) => {
  let {result, status, message} = await deleteSceneApi({id: node.id, type: node.type})
  if(status === 'success'){
    await queryTreeScenes();
  }
  layer.msg(message);
};
</script>

<style scoped>
.CheckRow {
  color: blue;
  text-decoration: underline;
}

.NoCheckRow {
  color: black;
  /*text-decoration: underline; */
}
</style>